﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Xml;
using Update.Utils.Interfaces;

namespace Update.Config
{
    /// <summary>
    /// 配置管理类
    /// </summary>
    public class ConfigManager : IConfigManager
    {
        private string _configFilePath;
        private Dictionary<string, string> _configValues;
        private bool _isLoaded;
        
        /// <summary>
        /// 调试模式
        /// </summary>
        public bool DebugMode { get; set; }
        
        /// <summary>
        /// 服务器URL
        /// </summary>
        public string ServerUrl { get; set; }
        
        /// <summary>
        /// 服务器类型
        /// </summary>
        public string ServerType { get; set; }
        
        /// <summary>
        /// 目标应用路径
        /// </summary>
        public string TargetAppPath { get; set; }
        
        /// <summary>
        /// 目标应用可执行文件
        /// </summary>
        public string TargetAppExe { get; set; }
        
        /// <summary>
        /// 本地版本
        /// </summary>
        public string LocalVersion { get; set; }
        
        /// <summary>
        /// 访问令牌
        /// </summary>
        public string AccessToken { get; set; }
        
        /// <summary>
        /// 仓库所有者
        /// </summary>
        public string RepoOwner { get; set; }
        
        /// <summary>
        /// 仓库名称
        /// </summary>
        public string RepoName { get; set; }
        
        /// <summary>
        /// 文件密码
        /// </summary>
        public string FilePwd { get; set; }
        
        /// <summary>
        /// 是否使用本地包
        /// </summary>
        public bool UseLocalPackage { get; set; }
        
        /// <summary>
        /// 本地包路径
        /// </summary>
        public string LocalPackagePath { get; set; }
        
        /// <summary>
        /// 模拟版本
        /// </summary>
        public string SimulateVersion { get; set; }
        
        /// <summary>
        /// 详细日志
        /// </summary>
        public bool VerboseLogging { get; set; }
        
        /// <summary>
        /// 强制覆盖文件
        /// </summary>
        public bool ForceOverwrite { get; set; }
        
        /// <summary>
        /// 自动结束占用进程
        /// </summary>
        public bool AutoTerminateProcesses { get; set; }
        
        /// <summary>
        /// 创建配置管理实例
        /// </summary>
        /// <param name="configFilePath">配置文件路径</param>
        public ConfigManager(string configFilePath)
        {
            _configFilePath = configFilePath;
            _configValues = new Dictionary<string, string>();
            _isLoaded = false;
            
            // 设置默认值
            DebugMode = false;
            ServerType = "Standard";
            UseLocalPackage = false;
            VerboseLogging = false;
            ForceOverwrite = true;
            AutoTerminateProcesses = true;
        }
        
        /// <summary>
        /// 加载配置
        /// </summary>
        /// <returns>是否成功加载</returns>
        public bool LoadConfig()
        {
            try
            {
                if (!File.Exists(_configFilePath))
                {
                    return false;
                }
                
                _configValues.Clear();
                
                // 读取XML配置文件
                XmlDocument doc = new XmlDocument();
                doc.Load(_configFilePath);
                
                XmlNode root = doc.DocumentElement;
                if (root == null)
                {
                    return false;
                }
                
                // 读取所有配置项
                foreach (XmlNode node in root.ChildNodes)
                {
                    if (node.NodeType == XmlNodeType.Element)
                    {
                        string key = node.Name;
                        string value = node.InnerText;
                        _configValues[key] = value;
                    }
                }
                
                // 读取基本配置
                ServerUrl = GetValue("ServerUrl", "");
                ServerType = GetValue("ServerType", "Standard");
                TargetAppPath = GetValue("TargetAppPath", "");
                TargetAppExe = GetValue("TargetAppExe", "");
                LocalVersion = GetValue("LocalVersion", "1.0.0.0");
                
                // 读取服务器特定配置
                AccessToken = GetValue("AccessToken", "");
                RepoOwner = GetValue("RepoOwner", "");
                RepoName = GetValue("RepoName", "");
                FilePwd = GetValue("FilePwd", "");
                
                // 读取调试配置
                DebugMode = GetBoolValue("Debug.Enabled", false);
                UseLocalPackage = GetBoolValue("Debug.UseLocalPackage", false);
                LocalPackagePath = GetValue("Debug.LocalPackagePath", "");
                SimulateVersion = GetValue("Debug.SimulateVersion", "");
                VerboseLogging = GetBoolValue("Debug.VerboseLogging", false);
                ForceOverwrite = GetBoolValue("Debug.ForceOverwrite", true);
                AutoTerminateProcesses = GetBoolValue("Debug.AutoTerminateProcesses", true);
                
                _isLoaded = true;
                return true;
            }
            catch
            {
                return false;
            }
        }
        
        /// <summary>
        /// 保存配置
        /// </summary>
        /// <returns>是否成功保存</returns>
        public bool SaveConfig()
        {
            try
            {
                XmlDocument doc = new XmlDocument();
                XmlDeclaration xmlDeclaration = doc.CreateXmlDeclaration("1.0", "UTF-8", null);
                
                XmlElement root = doc.CreateElement("Configuration");
                doc.AppendChild(xmlDeclaration);
                doc.AppendChild(root);
                
                // 基本配置
                AppendElement(doc, root, "ServerUrl", ServerUrl);
                AppendElement(doc, root, "ServerType", ServerType);
                AppendElement(doc, root, "TargetAppPath", TargetAppPath);
                AppendElement(doc, root, "TargetAppExe", TargetAppExe);
                AppendElement(doc, root, "LocalVersion", LocalVersion);
                
                // 服务器特定配置
                if (!string.IsNullOrEmpty(AccessToken))
                    AppendElement(doc, root, "AccessToken", AccessToken);
                
                if (!string.IsNullOrEmpty(RepoOwner))
                    AppendElement(doc, root, "RepoOwner", RepoOwner);
                
                if (!string.IsNullOrEmpty(RepoName))
                    AppendElement(doc, root, "RepoName", RepoName);
                
                if (!string.IsNullOrEmpty(FilePwd))
                    AppendElement(doc, root, "FilePwd", FilePwd);
                
                // 调试配置
                XmlElement debugElement = doc.CreateElement("Debug");
                root.AppendChild(debugElement);
                
                AppendElement(doc, debugElement, "Enabled", DebugMode.ToString());
                AppendElement(doc, debugElement, "UseLocalPackage", UseLocalPackage.ToString());
                
                if (!string.IsNullOrEmpty(LocalPackagePath))
                    AppendElement(doc, debugElement, "LocalPackagePath", LocalPackagePath);
                
                if (!string.IsNullOrEmpty(SimulateVersion))
                    AppendElement(doc, debugElement, "SimulateVersion", SimulateVersion);
                
                AppendElement(doc, debugElement, "VerboseLogging", VerboseLogging.ToString());
                AppendElement(doc, debugElement, "ForceOverwrite", ForceOverwrite.ToString());
                AppendElement(doc, debugElement, "AutoTerminateProcesses", AutoTerminateProcesses.ToString());
                
                // 保存文件
                doc.Save(_configFilePath);
                
                return true;
            }
            catch
            {
                return false;
            }
        }
        
        /// <summary>
        /// 更新配置值
        /// </summary>
        /// <param name="key">键</param>
        /// <param name="value">值</param>
        public void UpdateValue(string key, string value)
        {
            _configValues[key] = value;
            
            // 更新属性值
            switch (key)
            {
                case "ServerUrl":
                    ServerUrl = value;
                    break;
                case "ServerType":
                    ServerType = value;
                    break;
                case "TargetAppPath":
                    TargetAppPath = value;
                    break;
                case "TargetAppExe":
                    TargetAppExe = value;
                    break;
                case "LocalVersion":
                    LocalVersion = value;
                    break;
                case "AccessToken":
                    AccessToken = value;
                    break;
                case "RepoOwner":
                    RepoOwner = value;
                    break;
                case "RepoName":
                    RepoName = value;
                    break;
                case "FilePwd":
                    FilePwd = value;
                    break;
                case "Debug.Enabled":
                    DebugMode = bool.TryParse(value, out bool debugMode) ? debugMode : false;
                    break;
                case "Debug.UseLocalPackage":
                    UseLocalPackage = bool.TryParse(value, out bool useLocalPackage) ? useLocalPackage : false;
                    break;
                case "Debug.LocalPackagePath":
                    LocalPackagePath = value;
                    break;
                case "Debug.SimulateVersion":
                    SimulateVersion = value;
                    break;
                case "Debug.VerboseLogging":
                    VerboseLogging = bool.TryParse(value, out bool verboseLogging) ? verboseLogging : false;
                    break;
                case "Debug.ForceOverwrite":
                    ForceOverwrite = bool.TryParse(value, out bool forceOverwrite) ? forceOverwrite : true;
                    break;
                case "Debug.AutoTerminateProcesses":
                    AutoTerminateProcesses = bool.TryParse(value, out bool autoTerminateProcesses) ? autoTerminateProcesses : true;
                    break;
            }
        }
        
        /// <summary>
        /// 获取配置值
        /// </summary>
        /// <param name="key">键</param>
        /// <param name="defaultValue">默认值</param>
        /// <returns>配置值</returns>
        public string GetValue(string key, string defaultValue = "")
        {
            if (_configValues.TryGetValue(key, out string value))
            {
                return value;
            }
            
            return defaultValue;
        }
        
        /// <summary>
        /// 获取布尔值
        /// </summary>
        /// <param name="key">键</param>
        /// <param name="defaultValue">默认值</param>
        /// <returns>配置布尔值</returns>
        public bool GetBoolValue(string key, bool defaultValue = false)
        {
            if (_configValues.TryGetValue(key, out string value))
            {
                return bool.TryParse(value, out bool boolValue) ? boolValue : defaultValue;
            }
            
            return defaultValue;
        }
        
        /// <summary>
        /// 获取整数值
        /// </summary>
        /// <param name="key">键</param>
        /// <param name="defaultValue">默认值</param>
        /// <returns>配置整数值</returns>
        public int GetIntValue(string key, int defaultValue = 0)
        {
            if (_configValues.TryGetValue(key, out string value))
            {
                return int.TryParse(value, out int intValue) ? intValue : defaultValue;
            }
            
            return defaultValue;
        }
        
        /// <summary>
        /// 是否已加载
        /// </summary>
        public bool IsLoaded => _isLoaded;
        
        /// <summary>
        /// 配置文件路径
        /// </summary>
        public string ConfigFilePath => _configFilePath;
        
        /// <summary>
        /// 设置配置文件路径
        /// </summary>
        /// <param name="path">路径</param>
        public void SetConfigFilePath(string path)
        {
            _configFilePath = path;
        }
        
        /// <summary>
        /// 添加元素到XML文档
        /// </summary>
        private void AppendElement(XmlDocument doc, XmlElement parent, string name, string value)
        {
            XmlElement element = doc.CreateElement(name);
            element.InnerText = value;
            parent.AppendChild(element);
        }
    }
} 